package com.star.reply.scoring.strategy;

import cn.hutool.json.JSONUtil;
import com.baomidou.mybatisplus.core.toolkit.Wrappers;
import com.star.reply.model.dto.question.QuestionContentDTO;
import com.star.reply.model.entity.App;
import com.star.reply.model.entity.Question;
import com.star.reply.model.entity.ScoringResult;
import com.star.reply.model.entity.UserAnswer;
import com.star.reply.model.enums.AppScoringStrategyEnum;
import com.star.reply.model.enums.AppTypeEnum;
import com.star.reply.model.vo.QuestionVO;
import com.star.reply.scoring.ScoringStrategy;
import com.star.reply.scoring.ScoringStrategyConfig;
import com.star.reply.service.QuestionService;
import com.star.reply.service.ScoringResultService;
import org.springframework.stereotype.Component;

import javax.annotation.Resource;
import java.sql.Wrapper;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

/**
 * packageName com.star.reply.scoring.strategy
 *
 * @author zerostart
 * @className CustomTestScoringStrategy
 * @date 2024/9/11
 * @description 自定义测评类应用
 */

@ScoringStrategyConfig(appType = 1, scoringStrategy = 0)
public class CustomTestScoringStrategy implements ScoringStrategy {

    @Resource
    private QuestionService questionService;
    @Resource
    private ScoringResultService scoringResultService;

    @Override
    public UserAnswer doScore(List<String> choices, App app) throws Exception {
        Long appId = app.getId();
        // 1. 根据id查询题目信息和题目结果信息
        Question question = questionService.getOne(Wrappers.lambdaQuery(Question.class).
                eq(Question::getAppId, appId));

        List<ScoringResult> scoringResultList  = scoringResultService.list(
                Wrappers.lambdaQuery(ScoringResult.class)
                        .eq(ScoringResult::getAppId, appId)
        );
        //2. 统计用户选择的每一个结果的个数
        Map<String, Integer> optionCount = new HashMap<>();
        QuestionVO questionVO = QuestionVO.objToVo(question);
        List<QuestionContentDTO> questionContent = questionVO.getQuestionContent();
        // 2.1 遍历题目列表 [{options[{"score": 0,"value": "利马","key": "A"},{score:},] } ]
        for (QuestionContentDTO questionContentDTO : questionContent) {
            // 2.2 遍历用户答案列表 [A, B, C]
            for (String answer : choices) {
                //2.3 遍历题目中的选项   [{"result":"I","value":"独自工作","key":"A"}]
                for (QuestionContentDTO.Option option : questionContentDTO.getOptions()) {
                    //如果答案和和选项中的key匹配
                    if (answer.equals(option.getKey())) {
                        // 获取选项的result属性
                        String result = option.getResult();
                        // 如果result属性不在optionCount中，初始化为0
                        if (!optionCount.containsKey(result)) {
                            optionCount.put(result, 0);
                        }
                        // 在optionCount中增加计数
                        optionCount.put(result, optionCount.get(result) + 1);
                    }
                }
            }
        }
        //3. 遍历每种评分结果，计算哪个得分更高
        int maxScore = 0;
        //给默认值
        ScoringResult maxScoringResult = scoringResultList.get(0);

        for (ScoringResult scoringResult : scoringResultList) {
            List<String> resultProp = JSONUtil.toList(scoringResult.getResultProp(), String.class);
            // 计算当前评分结果的分数，[I, E] => [10, 5] => 15
            int score = resultProp.stream()
                    .mapToInt(prop -> optionCount.getOrDefault(prop, 0))
                    .sum();
            // 如果分数高于当前最高分数，更新最高分数和最高分数对应的评分结果

            if (score > maxScore) {
                maxScore = score;
                maxScoringResult = scoringResult;
            }
        }

        //4. 构造返回值，填充答案对象
        UserAnswer userAnswer = new UserAnswer();
        userAnswer.setAppId(appId);
        userAnswer.setAppType(app.getAppType());
        userAnswer.setScoringStrategy(app.getScoringStrategy());
        userAnswer.setChoices(JSONUtil.toJsonStr(choices));
        userAnswer.setResultId(maxScoringResult.getId());
        userAnswer.setResultName(maxScoringResult.getResultName());
        userAnswer.setResultDesc(maxScoringResult.getResultDesc());
        userAnswer.setResultPicture(maxScoringResult.getResultPicture());
        return userAnswer;
    }
}
